<template>
  <Dialog v-model:visible="visible" modal :header="title" :style="{ width: '90vw' }">
    <Panel>
      <template #header>
        <div class="flex items-center gap-2">
          <span class="font-bold">Server根配置</span>
        </div>
      </template>
      Server Name : <InputText v-model="editingServer.server" type="text" size="small" /> port:
      <InputNumber
        size="small"
        :useGrouping="false"
        v-model="editingServer.port"
        type="number"
        :max="60000"
        :min="1"
      />
      <Divider />
      <Chip v-for="(i, index) in editingServer.basicConfigs" :key="index">
        {{ i.code + '  ' + i.value + ';'
        }}<i class="pi pi-minus-circle" @click="basicConfigRemoveFn(i)" />
      </Chip>
      <Divider />
      <div class="flex gap-2">
        <basic-config-add :options="options" @confirm="basicConfigAddFn"></basic-config-add>
        <Button icon="pi pi-check" size="small" style="width: 120px" @click="addLocationFn"
          >+ Location</Button
        >
      </div>
    </Panel>
    <Divider align="left"> <b>Locations</b> </Divider>
    <Panel v-for="(i, index) in editingServer.locationConfigs" :key="index">
      <template #header> #{{ index + 1 }} </template>
      <Select
        v-model="i.modifier"
        :options="modifiers"
        optionLabel="name"
        option-value="value"
      ></Select>
      <InputText v-model="i.uri"></InputText>
      <Divider />
      <p v-for="(i2, index) in i.basicConfigs" :key="index" class="flex">
        <span class="flex-1"> {{ i2.code + '  ' + i2.value + ';' }}</span
        ><i class="pi pi-minus-circle" @click="locationBasicConfigRemoveFn(i2, i)" />
      </p>
      <Divider />
      <basic-config-add
        :options="basicConfigOptions"
        @confirm="addLocationBasicConfig($event, i)"
      ></basic-config-add>
    </Panel>
    <Divider />
    <template #footer>
      <Button label="Save" icon="pi pi-save" @click="newServerFn"  />
    </template>
  </Dialog>
</template>
<script setup lang="ts">
import BasicConfigAdd from '@/views/tools/nginx/detail-comps/basic-config-add.vue'
import type { BasicConfig, ServerConfig, ServerLocation } from '@/types/dt/Dt.ts'
import { ref } from 'vue'
import type { BasicConfigOption } from '@/views/tools/nginx/nginx-info.ts'
import { httpLocationBasicOptions, httpServerBasicOptions } from '@/views/tools/nginx/data/http_basic_options.ts'

const visible = ref(false)
const editingServer = ref<ServerConfig >({
  server: 'localhost',
  port: 5000,
  basicConfigs: [],
  locationConfigs: [],
})
const title = ref('')
let resolve : ((a: any) =>void) | undefined
let reject : ((e: Error) =>void) | undefined

const modifiers = [
  { name: '', value: '' },
  { name: '=', value: '=' },
  { name: '~', value: '~' },
]
const basicConfigOptions :BasicConfigOption[] = [
  ...httpLocationBasicOptions,
]
const options: BasicConfigOption[] = [
  ...httpServerBasicOptions
]

function basicConfigRemoveFn(e: BasicConfig) {
  editingServer.value.basicConfigs = editingServer.value.basicConfigs.filter((item) => item !== e)
}

function basicConfigAddFn(e: BasicConfig) {
  editingServer.value.basicConfigs.push(e)
}

function newServerFn() {
  if (typeof resolve === 'function') {
    resolve(editingServer.value)
  }
  visible.value = false
  editingServer.value = {
    server: 'localhost',
    port: 5000,
    basicConfigs: [],
    locationConfigs: [],
  }
  resolve = undefined
  reject = undefined
}

// add location
function addLocationFn() {
  editingServer.value!.locationConfigs.push({
    uri: '/',
    modifier: '',
    basicConfigs: [],
  })
}

function addLocationBasicConfig(e: BasicConfig, l: ServerLocation) {
  l.basicConfigs.push(e)
}

function locationBasicConfigRemoveFn(c: BasicConfig, l: ServerLocation) {
  l.basicConfigs = l.basicConfigs.filter((item) => item !== c)
}


function open(server?: ServerConfig) :Promise<ServerConfig> {
  if (server) {
    title.value = 'Edit Server'
    editingServer.value = JSON.parse(JSON.stringify(server))
  } else {
    title.value = 'Add Server'
    editingServer.value = {
      server: 'localhost',
      port: 5000,
      basicConfigs: [],
      locationConfigs: [],
    }
  }
  visible.value = true
  return new Promise((r, re) => {
    resolve = r;
    reject = re
  })
}

defineExpose({
  open: open
})
</script>
<style scoped></style>
